package com.huaxin.device.service.impl;

import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.core.metadata.IPage;
import com.baomidou.mybatisplus.core.toolkit.support.SFunction;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.huaxin.device.dto.ResponseCode;
import com.huaxin.device.dto.ResponseResult;
import com.huaxin.device.dto.request.ElectricalWellCreateReqDTO;
import com.huaxin.device.dto.request.ElectricalWellPageListReqDTO;
import com.huaxin.device.dto.request.ElectricalWellUpdateReqDTO;
import com.huaxin.device.mapper.ElectricalEquipmentMapper;
import com.huaxin.device.mapper.ElectricalWellMapper;
import com.huaxin.device.mapping.ElectricalWellMapping;
import com.huaxin.device.models.ElectricalWell;
import com.huaxin.device.service.ElectricalWellService;
import lombok.RequiredArgsConstructor;
import org.springframework.context.ApplicationContext;
import org.springframework.stereotype.Service;
import org.webjars.NotFoundException;

import static org.springframework.util.StringUtils.hasText;

@Service
@RequiredArgsConstructor
public class ElectricalWellServiceImpl extends ServiceImpl<ElectricalWellMapper, ElectricalWell> implements ElectricalWellService {

    private final ApplicationContext applicationContext;
    private final ElectricalWellMapping mapping;
    private final ElectricalWellMapper mapper;
    private final ElectricalEquipmentMapper electricalEquipmentMapper;

    @Override
    public ResponseResult<ElectricalWell> create(ElectricalWellCreateReqDTO in) {
        if (in == null) {
            return ResponseResult.parameterError(null, "参数不能为空");
        }

        // 校验 wellCode + familyId + orgId 是否已存在
        if (existsByFields(ElectricalWell::getWellCode, in.getWellCode(), in.getFamilyId(), in.getOrgId(), null)) {
            return ResponseResult.failure(ResponseCode.CONFLICT, "编号已存在", null);
        }
        // 校验 wellName + familyId + orgId 是否已存在
        if (existsByFields(ElectricalWell::getWellName, in.getWellName(), in.getFamilyId(), in.getOrgId(), null)) {
            return ResponseResult.failure(ResponseCode.CONFLICT, "名称已存在", null);
        }

        ElectricalWell entity = mapping.toEntity(in);
        if (!save(entity)) {
            return ResponseResult.failure(ResponseCode.INTERNAL_SERVER_ERROR, "创建失败，请稍后重试", null);
        }
        return ResponseResult.ok(getById(entity.getId()));
    }

    @Override
    public ElectricalWell getByWellId(String id) {
        if (!hasText(id)) {
            throw new IllegalArgumentException("ID不能为空");
        }
        ElectricalWell entity = getById(id);
        if (entity == null) {
            throw new NotFoundException("电井不存在");
        }
        return entity;
    }

    @Override
    public ResponseResult<String> update(ElectricalWellUpdateReqDTO in) {
        if (in == null) {
            return ResponseResult.parameterError(null, "参数不能为空");
        }

        ElectricalWell entity = getByWellId(in.getId());

        // 校验 wellCode + familyId + orgId 是否已存在（不包含当前ID）
        if (existsByFields(ElectricalWell::getWellCode, in.getWellCode(), in.getFamilyId(), in.getOrgId(), entity.getId())) {
            return ResponseResult.failure(ResponseCode.CONFLICT, "编号已存在", null);
        }
        // 校验 wellName + familyId + orgId 是否已存在（不包含当前ID）
        if (existsByFields(ElectricalWell::getWellName, in.getWellName(), in.getFamilyId(), in.getOrgId(), entity.getId())) {
            return ResponseResult.failure(ResponseCode.CONFLICT, "名称已存在", null);
        }

        mapping.updateEntity(in, entity);
        if (!updateById(entity)) {
            return ResponseResult.failure(ResponseCode.INTERNAL_SERVER_ERROR, "更新失败，请稍后重试", null);
        }
        return ResponseResult.ok("更新成功");
    }

    @Override
    public ResponseResult<String> delete(String id) {
        ElectricalWell entity = getByWellId(id);

        // 检查该电井下是否有设备
        if (electricalEquipmentMapper.existsByWellId(entity.getId())) {
            return ResponseResult.failure(ResponseCode.CUSTOM_BUSINESS_ERROR, "该电井下有设备，请先删除设备", null);
        }

        boolean removed = this.applicationContext.getBean(ElectricalWellService.class).removeById(id);
        if (!removed) {
            return ResponseResult.failure(ResponseCode.INTERNAL_SERVER_ERROR, "删除失败，请稍后重试", null);
        }
        return ResponseResult.ok("删除成功");
    }

    @Override
    public ResponseResult<IPage<ElectricalWell>> pageQuery(ElectricalWellPageListReqDTO in) {
        if (in == null) {
            return ResponseResult.parameterError(null, "参数错误");
        }

        IPage<ElectricalWell> page = new Page<>(in.getPageNum(), in.getPageSize());
        LambdaQueryWrapper<ElectricalWell> wrapper = new LambdaQueryWrapper<>();

        if (hasText(in.getWellName())) {
            wrapper.like(ElectricalWell::getWellName, in.getWellName());
        }
        if (hasText(in.getWellCode())) {
            wrapper.like(ElectricalWell::getWellCode, in.getWellCode());
        }
        if (hasText(in.getLocation())) {
            wrapper.like(ElectricalWell::getLocation, in.getLocation());
        }
        if (hasText(in.getWaterproofGrade())) {
            wrapper.eq(ElectricalWell::getWaterproofGrade, in.getWaterproofGrade());
        }
        if (in.getFireDoorExists() != null) {
            wrapper.eq(ElectricalWell::getFireDoorExists, in.getFireDoorExists());
        }
        if (hasText((in.getOrgId()))) {
            wrapper.eq(ElectricalWell::getOrgId, in.getOrgId());
        }
        if (hasText(in.getFamilyId())) {
            wrapper.eq(ElectricalWell::getFamilyId, in.getFamilyId());
        }

        wrapper.orderByDesc(ElectricalWell::getCreatedAt);
        IPage<ElectricalWell> result = page(page, wrapper);
        return ResponseResult.ok(result);
    }

    /**
     * 检查多个字段值组合是否已存在（排除当前ID）
     *
     * @param fieldGetter 字段Getter
     * @param fieldValue  字段值
     * @param familyId    家庭ID
     * @param orgId       组织ID
     * @param excludeId   要排除的ID（可为null）
     * @return 是否存在匹配记录
     */
    private boolean existsByFields(
            SFunction<ElectricalWell, ?> fieldGetter,
            Object fieldValue,
            String familyId,
            String orgId,
            String excludeId) {

        if (fieldGetter == null) return false;

        LambdaQueryWrapper<ElectricalWell> wrapper = new LambdaQueryWrapper<>();

        if (fieldValue == null ||
                (fieldValue instanceof CharSequence cs && cs.toString().trim().isEmpty())) {
            wrapper.and(wrapper1 -> wrapper1
                    .isNull(fieldGetter)
                    .or().eq(fieldGetter, "")
            );
        } else {
            wrapper.eq(fieldGetter, fieldValue.toString().trim());
        }

        if (familyId == null || familyId.trim().isEmpty()) {
            wrapper.and(wrapper1 -> wrapper1
                    .isNull(ElectricalWell::getFamilyId)
                    .or().eq(ElectricalWell::getFamilyId, "")
            );
        } else {
            wrapper.eq(ElectricalWell::getFamilyId, familyId.trim());
        }

        if (orgId == null || orgId.trim().isEmpty()) {
            wrapper.and(wrapper1 -> wrapper1
                    .isNull(ElectricalWell::getOrgId)
                    .or().eq(ElectricalWell::getOrgId, "")
            );
        } else {
            wrapper.eq(ElectricalWell::getOrgId, orgId.trim());
        }

        if (excludeId != null && !excludeId.trim().isEmpty()) {
            wrapper.ne(ElectricalWell::getId, excludeId.trim());
        }

        return this.count(wrapper) > 0;
    }
}